using System;
using System.Collections.Generic;
using System.Text;
using System.Data;
using SubSonic;

using Impact.Infrastructure.Exceptions;
using Impact.Model.Service;
using StructureMap;
using Impact.Model.Objects;

namespace Impact.Controllers
{
    /// <summary>
    /// this controller is responsible for managing the logic on the "pages" view of the admin
    /// </summary>
    public class PageController
    {
        private Guid userId;
        private IPageService service;

        /// <summary>
        /// default constructor
        /// </summary>
        /// <param name="userId">the id of the user currently using the page editor</param>
        public PageController(Guid userId)
        {
            Check.Require(!userId.Equals(Guid.Empty), "A valid user ID is required");
            this.userId = userId;
            this.service = ObjectFactory.GetInstance<IPageService>();
        }

        /// <summary>
        /// performs startup functionality
        /// </summary>
        public void Initialize()
        {
        }

        /// <summary>
        /// returns a list of all pages in the system, regardless of whether the page is enabled
        /// </summary>
        /// <returns></returns>
        public ImpactPageCollection GetPages()
        {
            return service.FetchAllPages(false);
        }

        /// <summary>
        /// returns a list of pages in the system that are of the given type
        /// </summary>
        /// <returns></returns>
        public TemplateCollection GetTemplates()
        {
            return service.FetchAllTemplates();
        }

        /// <summary>
        /// deletes the page given
        /// </summary>
        public void DeletePage(int pageId)
        {
            Check.Require(pageId, "PageId is required");
            service.Remove(pageId);
        }

        /// <summary>
        /// this method increases the order the given page is presented in by one.  
        /// the first page shown (top of screen) is the lowest sequence number.
        /// the last page shown (bottom of screen) is the highest sequence number.
        /// </summary>
        public void IncrementSequence(int pageId)
        {
            Check.Require(pageId, "PageId is required");
            ImpactPage page = service.FetchByID(pageId);
            Check.Require(ImpactPage.IsValid(page), "Page not found");
            page.Sequence += 11;
            // save with no username so "modifiedBy" column is not updated
            service.Save(page);

            SortPages();
        }

        /// <summary>
        /// this method decreases the order the given page is presented in by one.  
        /// the first page shown (top of screen) is the lowest sequence number.
        /// the last page shown (bottom of screen) is the highest sequence number.
        /// </summary>
        public void DecrementSequence(int pageId)
        {
            Check.Require(pageId, "PageId is required");
            ImpactPage page = service.FetchByID(pageId);
            Check.Require(ImpactPage.IsValid(page), "Page not found");
            page.Sequence -= 11;
            // save with no username so "modifiedBy" column is not updated
            service.Save(page);

            SortPages();
        }

        /// <summary>
        /// flip the enabled flag on the given page
        /// </summary>
        public void ToggleEnabled(int pageId)
        {
            Check.Require(pageId, "PageId is required");
            ImpactPage page = service.FetchByID(pageId);
            Check.Require(ImpactPage.IsValid(page), "Page not found");
            page.Enabled = !page.Enabled;
            // save with no username so "modifiedBy" column is not updated
            service.Save(page);
        }

        /// <summary>
        /// re-label all page sequence numbers so they are consistent
        /// </summary>
        private void SortPages()
        {
            int count = 0;
            IPageService service = ObjectFactory.GetInstance<IPageService>();

            ImpactPageCollection pages = service.FetchAllPages(true);
            foreach ( ImpactPage page in pages )
            {
                page.Sequence = ++count * 10;
                // save with no username so "modifiedBy" column is not updated
                service.Save( page );
            }


        }

    }
}
